package gui;

import org.jnativehook.GlobalScreen;
import org.jnativehook.NativeHookException;
import org.jnativehook.keyboard.NativeKeyEvent;
import org.jnativehook.keyboard.NativeKeyListener;
import org.jnativehook.mouse.NativeMouseEvent;
import org.jnativehook.mouse.NativeMouseInputListener;
import org.jnativehook.mouse.NativeMouseWheelEvent;
import org.jnativehook.mouse.NativeMouseWheelListener;

import java.awt.AWTException;
import java.awt.Component;
import java.awt.Image;
import java.awt.Robot;
import java.awt.event.ActionEvent;
import java.awt.event.InputEvent;
import java.awt.event.ItemEvent;
import java.awt.event.ItemListener;
import java.awt.event.KeyEvent;
import java.awt.event.WindowEvent;
import java.awt.event.WindowListener;
import java.util.ArrayList;

import java.awt.event.*;
import javax.swing.*;

import model.getInfo;
import model.robot;
import ctrl.*;
import javax.swing.JButton;
import javax.swing.JMenuBar;
import javax.swing.GroupLayout;
import javax.swing.GroupLayout.Alignment;
import javax.swing.JMenu;
import javax.swing.JMenuItem;
import javax.swing.KeyStroke;


public class robotUI extends JFrame implements ActionListener, NativeMouseInputListener, NativeMouseWheelListener, WindowListener, NativeKeyListener{

	private ArrayList<getInfo> infor = new ArrayList<getInfo>();
	private robot rob = new robot();
	private getInfo info = new getInfo();
	private infoCtrl infoCtrl = new infoCtrl();
	private robotCtrl robCtrl = new robotCtrl();
	private boolean done;
	
	private int delay = 500;
	private boolean recorded;
	
	private JPanel contentPane;
	private JPanel buttonArea;
	
	private boolean record;
	private boolean play;
	
	JMenuItem mntmRecord;
	JMenuItem mntmStopRecord;
	JMenuItem mntmStart;
	JMenuItem mntmStop;
	JMenuItem mntmExit;
	
	Image image = null;
	private JButton btnStopRecord;
	
	
	public static void main(String[] args)
	{
		robotUI roboUI = new robotUI();
		try {
            GlobalScreen.registerNativeHook();
    }
    catch (NativeHookException ex) {
            System.err.println("There was a problem registering the native hook.");
            System.err.println(ex.getMessage());

            System.exit(1);
    }
		 
		 GlobalScreen.getInstance().addNativeMouseListener(roboUI);
        GlobalScreen.getInstance().addNativeMouseMotionListener(roboUI);
        GlobalScreen.getInstance().addNativeKeyListener(roboUI);
        GlobalScreen.getInstance().addNativeMouseWheelListener(roboUI);
		
	
	}
	
	
	
	robotUI()
	{
		infoCtrl.setInfo(info);
		record = false;
	    play = false;
		done = false;
		recorded = false;
		infoCtrl.setRecord(false);
		robCtrl.setRobot(rob);
	
	setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
	setBounds(100, 100, 600, 700);
	setLocationRelativeTo(null);
	

	setResizable(false);
	
	contentPane = new JPanel();
	buttonArea = new JPanel();
	
	setContentPane(contentPane);
	
	JMenuBar menuBar = new JMenuBar();
	setJMenuBar(menuBar);
	
	
	JMenu mnRobotOptions = new JMenu("Robot Options");
	menuBar.add(mnRobotOptions);
	mnRobotOptions.setMnemonic(KeyEvent.VK_F);
	
	
	mntmRecord = new JMenuItem("Record");
	mnRobotOptions.add(mntmRecord);
	mntmRecord.addActionListener(this);
	mntmRecord.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_R, ActionEvent.ALT_MASK));
	mntmRecord.getAccessibleContext().setAccessibleDescription("Start Record");
	
	mntmStopRecord = new JMenuItem("Stop Record");
	mnRobotOptions.add(mntmStopRecord);
	mntmRecord.addActionListener(this);
	mntmStopRecord.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_S, ActionEvent.ALT_MASK));
	mntmStopRecord.getAccessibleContext().setAccessibleDescription("Stop Record");
	
	
	mntmStart = new JMenuItem("Start");
	mntmStart.addActionListener(this);
	mntmStart.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_S, ActionEvent.CTRL_MASK));
	mntmStart.getAccessibleContext().setAccessibleDescription("Stop Record");
	mnRobotOptions.add(mntmStart);
	
	mntmStop = new JMenuItem("Stop");
	mntmStop.addActionListener(this);
	mntmStop.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_D, ActionEvent.CTRL_MASK));
	mntmStop.getAccessibleContext().setAccessibleDescription("Stop Record");
	mnRobotOptions.add(mntmStop);
	
	mntmExit = new JMenuItem("Exit");
	mntmExit.addActionListener(this);
	mntmExit.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_F4, ActionEvent.ALT_MASK));
	mntmExit.getAccessibleContext().setAccessibleDescription("Stop Record");
	mnRobotOptions.add(mntmExit);
	
	getContentPane().setLayout(null);
	
	JButton btnRecord = new JButton("Record");
	//btnRecord.setMnemonic(KeyEvent.VK_R);
	btnRecord.addActionListener(new ActionListener() {
		public void actionPerformed(ActionEvent e) {
			infor.clear();
			infoCtrl.setRecord(true);
			record = true;
			
	//		setState(ICONIFIED);
		}
	});
	btnRecord.setBounds(243, 37, 119, 23);
	contentPane.add(btnRecord);
	
	btnStopRecord = new JButton("Stop Record");
	btnStopRecord.setMnemonic(KeyEvent.VK_F);
	btnStopRecord.setBounds(243, 71, 119, 23);
	btnStopRecord.addActionListener(new ActionListener(){
		public void actionPerformed(ActionEvent e)
		{
	//		setState(NORMAL);
			
			for(int i = 0; i < infor.size(); i++)
			{
				System.out.println(infor.get(i).getX());
			}
			infoCtrl.setRecord(false);
			record = false;
		}
		
	});
	contentPane.add(btnStopRecord);
	
	JButton btnPlay = new JButton("Play");
	btnPlay.setBounds(243, 105, 119, 23);
	btnPlay.addActionListener(new ActionListener()
	{
		public void actionPerformed(ActionEvent e)
		{
			done = false;
			infoCtrl.setDone(false);
			robotnik();
		}
	});
	contentPane.add(btnPlay);
	
	JButton btnNewButton = new JButton("Stop Play");
	btnNewButton.setMnemonic(KeyEvent.VK_R);
	btnNewButton.addActionListener(new ActionListener()
	{
		public void actionPerformed(ActionEvent e)
		{
			done = false;
			infoCtrl.setDone(false);
			
		}
	}
			
			);
	btnNewButton.setBounds(243, 139, 119, 23);
	contentPane.add(btnNewButton);
	
	JButton btnExit = new JButton("Exit");
	btnExit.setMnemonic(KeyEvent.VK_F4);
	btnExit.addActionListener(new ActionListener()
	{
		public void actionPerformed(ActionEvent e)
		{
			System.exit(0);
		}
	});
	
	btnExit.setBounds(243, 173, 119, 23);
	contentPane.add(btnExit);
	
		System.out.println("Size is : " + infor.size() + " ");
	setVisible(true);
	
//	if(record == true)
	}


	@Override
	public void actionPerformed(ActionEvent e) {
		// TODO Auto-generated method stub
		if(e.getSource() == mntmRecord)
		{
			
				infoCtrl.setRecord(true);
				System.out.println(infoCtrl.getRecord());
			
		}
		else if(e.getSource() == mntmStopRecord )
		{
			
				record = false;
				System.out.println(record);
			
		}
		else if(e.getSource() == mntmStart)
		{
			{
				play = true;
			}
		}
		else if(e.getSource() == mntmStop)
		{
			{
				play = false;
			}
		}
		else if(e.getSource() == mntmExit)
		{
			done = true;
			System.exit(0);
		}
		
	}



	@Override
	public void nativeMouseClicked(NativeMouseEvent e) {
		// TODO Auto-generated method stub
		
	}



	@Override
	public void nativeMousePressed(NativeMouseEvent e) {
		
		if(record == true)
		{
			recorded = true;
			infoCtrl infoCtrl2 = new infoCtrl();
			getInfo inf = new getInfo();
			infoCtrl2.setInfo(inf);
			infoCtrl2.setX(e.getX());
			infoCtrl2.setY(e.getY());
			if(e.getButton() == 1)
			{
			System.out.println("Mouse Left pressed LOL");
			infoCtrl2.setLeftClickPress(true);
			infoCtrl2.setLeftClickRelease(false);
			System.out.println(infoCtrl2.getLeftClickRelease());
			System.out.println(infoCtrl.isLeftClickPressed());
			System.out.println(infoCtrl2.getX());
			System.out.println(infoCtrl2.getY());
			}
			else if (e.getButton() == 2)
			{
				System.out.println("Mouse Right pressed LOL");
				infoCtrl2.setRightClickPress(true);
				infoCtrl2.setRightClickRelease(false);
				System.out.println(infoCtrl2.getX());
				System.out.println(infoCtrl2.getY());
			}
			infor.add(inf);
			System.out.println(infor.size());
			System.out.println(infor.get(0).isLeftClickPress());
		//	infoCtrl2.cleanUp();
			
			
		}
		
		
	}



	@Override
	public void nativeMouseReleased(NativeMouseEvent e) {
		if(record == true)
		{
			infoCtrl infoCtrl2 = new infoCtrl();
			getInfo inf = new getInfo();
			infoCtrl2.setInfo(inf);
			recorded = true;
			infoCtrl2.setX2(e.getX());
			infoCtrl2.setY2(e.getY());
			if(e.getButton() == 1)
			{
			System.out.println("Mouse Left released LOL");
			infoCtrl2.setLeftClickPress(false);
			infoCtrl2.setLeftClickRelease(true);
			System.out.println(infoCtrl2.getLeftClickRelease());
			System.out.println(infoCtrl.isLeftClickPressed());
			System.out.println(infoCtrl2.getX2());
			System.out.println(infoCtrl2.getY2());
			}
			else if (e.getButton() == 2)
			{
				System.out.println("Mouse Right released LOL");
				infoCtrl2.setRightClickPress(false);
				infoCtrl2.setRightClickRelease(true);
				System.out.println(infoCtrl2.getX2());
				System.out.println(infoCtrl2.getY2());
			}
			
			infor.add(inf);
			System.out.println(infor.size());	
			
		//	infoCtrl.cleanUp();
			
		}
	}



	@Override
	public void nativeMouseDragged(NativeMouseEvent arg0) {
		// TODO Auto-generated method stub
		
	}



	@Override
	public void nativeMouseMoved(NativeMouseEvent arg0) {
		// TODO Auto-generated method stub
		
	}



	@Override
	public void nativeKeyPressed(NativeKeyEvent e) {
		if(record == true)
		{
			infoCtrl infoCtrl2 = new infoCtrl();
			getInfo inf = new getInfo();
			infoCtrl2.setInfo(inf);
			recorded = true;
			infoCtrl2.setKey(e.getKeyCode());
			System.out.println("Key Pressed: " + NativeKeyEvent.getKeyText(e.getKeyCode()));
			infoCtrl2.setKeyPress(true);
			infoCtrl2.setKeyRelease(false);
			infor.add(inf);
			System.out.println(infor.size());
		//	infoCtrl2.cleanUp();
		}
		
	}

	public void robotnik()
	{
		infoCtrl infoCtrl2 = new infoCtrl();
		getInfo inf = new getInfo();
		infoCtrl2.setInfo(inf);
		
		System.out.println("Test robotnik");
 //   	while(done == false)
//	{
		for(int i = 0 ; i < infor.size() - 2; i++)
		{
		
		inf = infor.get(i);
		System.out.println(inf.getX());
		System.out.println(inf.getY());
		System.out.println("Test robotnik for");
		boolean leftClick = infoCtrl2.isLeftClickPressed();
		boolean rightClick = infoCtrl2.isRightClickPressed();
		boolean keyPressed = infoCtrl2.isKeyPressed();
		boolean leftRelease = infoCtrl2.getLeftClickRelease();
		boolean rightRelease = infoCtrl2.getRightClickRelease();
		boolean keyReleased = infoCtrl2.getKeyReleased();
		int wheelDir = infoCtrl2.getWheelDir();
		int wheelAm = infoCtrl2.getWheelAmount();
		
		System.out.println(leftClick);
		System.out.println(rightClick);
		System.out.println(keyPressed);
		System.out.println(leftRelease);
		System.out.println(rightRelease);
		System.out.println(keyReleased);
		System.out.println(wheelAm);
		System.out.println(wheelDir);
		if(leftClick == true)
		{
			System.out.println("Test robotnik click");
			robCtrl.setDelay(delay);
			robCtrl.moveMouseTo(infoCtrl2.getX(), infoCtrl2.getY());
			robCtrl.setDelay(delay);
			robCtrl.leftClick();
			robCtrl.setDelay(delay);
		}
		else if (leftClick == false && leftRelease == true && rightClick == false && keyPressed == false)
		{
			System.out.println("Test robotnik click release");
			robCtrl.setDelay(delay);
			robCtrl.moveMouseTo(infoCtrl2.getX2(), infoCtrl2.getY2());
			robCtrl.setDelay(delay);
			robCtrl.leftRelease();
			robCtrl.setDelay(delay);
		}
		else if (rightClick == true)
		{
			System.out.println("Test robotnik right click");
			robCtrl.setDelay(delay);
			robCtrl.moveMouseTo(infoCtrl2.getX(), infoCtrl2.getY());
			robCtrl.setDelay(delay);
			robCtrl.rightClick();
			robCtrl.setDelay(delay);
		}
		else if(leftClick == false && rightRelease == true  && rightClick == false && keyPressed == false)
		{
			System.out.println("Test robotnik right click release");
			robCtrl.setDelay(delay);
			robCtrl.moveMouseTo(infoCtrl2.getX2(), infoCtrl2.getY2());
			robCtrl.setDelay(delay);
			robCtrl.rightRelease();
			robCtrl.setDelay(delay);
		}
		else if (keyPressed == true)
		{
			System.out.println("Test robotnik key");
			robCtrl.setDelay(delay);
			robCtrl.pressK(infoCtrl2.getKey());
			robCtrl.setDelay(delay);
		}
		else if (keyPressed == false && leftClick == false && rightRelease == false
				&& rightClick == false && leftRelease == false && keyReleased == true )
		{
			System.out.println("Test robotnik key release");
			robCtrl.setDelay(delay);
			robCtrl.releaseK(infoCtrl2.getKey());
			robCtrl.setDelay(delay);
		}
		else if (recorded == false)
				{
			System.out.println("Test robotnik recorded false");
			done = true;
			Component frame = null;
			JOptionPane.showMessageDialog(frame,
				    "You did not previously record your actions");
			
				}
	}
		
//	}
		
	}


	@Override
	public void nativeKeyReleased(NativeKeyEvent e) {
		if(record == true)
		{
			infoCtrl infoCtrl2 = new infoCtrl();
			getInfo inf = new getInfo();
			infoCtrl2.setInfo(inf);
			recorded = true;
			infoCtrl2.setKey(e.getKeyCode());
			System.out.println("Key Released: " + NativeKeyEvent.getKeyText(e.getKeyCode()));
			infoCtrl2.setKeyPress(false);
			infoCtrl2.setKeyRelease(true);
			infor.add(inf);
			System.out.println(infor.size());	
		//	infoCtrl2.cleanUp();
		}
		
	}



	@Override
	public void nativeKeyTyped(NativeKeyEvent arg0) {
		// TODO Auto-generated method stub
		
	}



	@Override
	public void windowActivated(WindowEvent e) {
		// TODO Auto-generated method stub
		
	}



	@Override
	public void windowClosed(WindowEvent e) {
		// TODO Auto-generated method stub
		
	}



	@Override
	public void windowClosing(WindowEvent e) {
		// TODO Auto-generated method stub
		
	}



	@Override
	public void windowDeactivated(WindowEvent e) {
		// TODO Auto-generated method stub
		
	}



	@Override
	public void windowDeiconified(WindowEvent e) {
		// TODO Auto-generated method stub
		
	}



	@Override
	public void windowIconified(WindowEvent e) {
		// TODO Auto-generated method stub
		
	}



	@Override
	public void windowOpened(WindowEvent e) {
		// TODO Auto-generated method stub
		
	}



	@Override
	public void nativeMouseWheelMoved(NativeMouseWheelEvent e) {
		if(record == true)
		{
			infoCtrl infoCtrl2 = new infoCtrl();
			getInfo inf = new getInfo();
			infoCtrl2.setInfo(inf);
			recorded = true;
			infoCtrl2.setWheelAm(e.getScrollAmount());
			infoCtrl2.setWheelDir(e.getWheelRotation());
			infoCtrl2.setKeyPress(true);
			infor.add(inf);
			System.out.println(infor.size());	
	//		infoCtrl2.cleanUp();
		}
		
	}
}